/*global pi, Worker */

/**
 * 派发和接收消息的封装函数
 */

pi.mod.define('pi.worker.handle', function (pi) {
	"use strict";
	var loadWorker, parseWorker, renderWorker, computeWorker, nextID = 0,
		// 最大ID=2^31，超过了就从头来过
		maxID = 2147483648,
		idCallbackTable = [],
		module = {};

	/* 初始化消息模块，创建线程 */
	module.init = function () {
		loadWorker = pi.lang.createWorker("pi.worker.load");
		computeWorker = pi.lang.createWorker("pi.worker.compute");
		parseWorker = pi.lang.createWorker("pi.worker.parse");
		renderWorker = pi.lang.createWorker("pi.worker.render");
		loadWorker.onmessage = computeWorker.onmessage = parseWorker.onmessage = renderWorker.onmessage = function (e) {
			var callback, data = e.data;
			if (pi.lang.isObject(data)) {
				callback = idCallbackTable[data.id];
				if (callback && pi.lang.isFunction(callback)) {
					callback(data.data);
				} else {
					pi.log("worker.onmessage error: type =" + data.type + ", id = " + data.id + ", data = " + data.data);
				}
				if (callback !== undefined) {
					delete idCallbackTable[data.id];
				}
			}
		};

		module.clear = function () {
			loadWorker.postMessage("quit");
			computeWorker.postMessage("quit");
			parseWorker.postMessage("quit");
			renderWorker.postMessage("quit");
		};

		loadWorker.onerror = computeWorker.onerror = parseWorker.onerror = renderWorker.onerror = function (e) {
			pi.log("worker error: msg = " + e.message + ", file = " + e.filename + ", line = " + e.lineno);
		};
	};

	/**
	 * 向worker发送消息{type: typeName, id: nextID, data: param}
	 */

	function postMsg(worker, typeName, callback, param) {
		if (idCallbackTable[nextID] !== undefined) {
			return;
		}
		if (callback) {
			idCallbackTable[nextID] = callback;
		}
		worker.postMessage({
			type: typeName,
			id: nextID,
			data: param
		});

		nextID += 1;
		if (nextID > maxID) {
			nextID = 1;
		}
	}

	/********************* 加载线程的消息 *********************/

	/**
	 * 加载文件
	 * path：string，文件vfs路径
	 * callback: 带一个参数的函数，处理worker发送过来的回应数据
	 */
	module.load = function (path, callback) {
		postMsg(loadWorker, "load", callback, path);
	};

	/********************* 解析线程的消息 *********************/

	/**
	 * 创建图像
	 * data: {
	 *		data: int, 数据句柄
	 *		size: int, 数据的字节数
	 *		param: 字符串,
	 *			"[["hue", alpha1, alpha2, value],
	 *			["bright", alpha1, alpha2, value],
	 *			["gray", alpha1, alpha2],
	 *			...]"
	 * }
	 * callback: 带一个参数的函数，处理worker发送过来的回应数据
	 */
	module.loadImg = function (data, callback) {
		delete data.param;
		postMsg(parseWorker, "loadImg", callback, data);
	};

	/** 解析字体
	 * data: {
	 *		data: int, 数据句柄
	 *		size: int, 数据的字节数
	 *		param:
	 * }
	 * callback: 带一个参数的函数，处理worker发送过来的回应数据
	 */
	module.createFont = function (data, callback) {
		postMsg(parseWorker, "createFont", callback, data);
	};


	/**
	 * 解析网格
	 * data: {
	 *		data: int, 数据句柄
	 *		size: int, 数据的字节数
	 * }
	 * callback: 带一个参数的函数，处理worker发送过来的回应数据
	 */
	module.loadMesh = function (data, callback) {
		postMsg(parseWorker, "loadMesh", callback, data);
	};

	/**
	 * 解析骨骼
	 * data: {
	 *		data: int, 数据句柄
	 *		size: int, 数据的字节数
	 * }
	 * callback: 带一个参数的函数，处理worker发送过来的回应数据
	 */
	module.createSkeleton = function (data, callback) {
		postMsg(parseWorker, "createSkeleton", callback, data);
	};

	/**
	 * 解析天空盒
	 * callback: 带一个参数的函数，处理worker发送过来的回应数据
	 */
	module.createSkybox = function (callback) {
		postMsg(parseWorker, "createSkybox", callback, undefined);
	};

	/**
	 * 解析地形
	 * data: {
	 *		width: int 平坦宽度
	 *		depth: int 平坦深度,
	 *		posTable: RefResource, 数据句柄, 每个单位的位置数据
	 *		sx: float, 宽度每单位代表多少像素
	 *		sy: float, 高度每单位代表多少像素
	 *		sz: float, 深度每单位代表多少像素
	 * }
	 * callback: 带一个参数的函数，处理worker发送过来的回应数据
	 */
	module.createTerrain = function (data, callback) {
		postMsg(parseWorker, "createTerrain", callback, data);
	};

	/********************* 计算线程的消息 *********************/

	/**
	 * 计算消息
	 * data: {
	 *		context: int 渲染环境句柄,
	 *		handle: int 字节缓冲的句柄
	 * }
	 * callback: 带一个参数的函数，处理worker发送过来的回应数据
	 */
	module.compute = function (data, callback) {
		postMsg(computeWorker, "compute", callback, data);
	};

	/********************* 渲染线程的消息 *********************/

	/**
	 * 创建渲染环境
	 * windowHandle: int window句柄
	 * callback: 带一个参数的函数，处理worker发送过来的回应数据
	 */
	module.createContext = function (windowHandle, callback) {
		postMsg(renderWorker, "createContext", callback, windowHandle);
	};

	/**
	 * 创建纹理渲染环境
	 * data {
	 *		width: int 宽度,
	 *		height: int 高度
	 * }
	 * callback: 带一个参数的函数，处理worker发送过来的回应数据
	 */
	module.createTexContext = function (data, callback) {
		postMsg(renderWorker, "createTexContext", callback, data);
	};

	/**
	 * 销毁渲染环境
	 * context: int, 渲染环境句柄
	 * callback: 带一个参数的函数，处理worker发送过来的回应数据
	 */
	module.destroyContext = function (context, callback) {
		postMsg(renderWorker, "destroyContext", callback, context);
	};

	/**
	 * 创建空纹理
	 * width, height: 宽、高
	 * callback: {
	 *		fun: function 二元函数, 第一个参数是context，第二个参数是data
	 *		context: fun的上下文
	 * }
	 */
	module.createTex = function (w, h, callback) {
		var data = {
			width: w,
			height: h
		};
		postMsg(renderWorker, "createTex", callback, data);
	};

	/**
	 * 从图片创建纹理
	 * img: int，图像句柄
	 * callback: {
	 *		fun: function 二元函数, 第一个参数是context，第二个参数是data
	 *		context: fun的上下文
	 * }
	 */
	module.loadTex = function (img, callback) {
		postMsg(renderWorker, "loadTex", callback, img);
	};

	/**
	 * 用图片更新纹理
	 * img: int，图像句柄
	 * tex: int, 纹理句柄
	 * callback: {
	 *		fun: function 二元函数, 第一个参数是context，第二个参数是data
	 *		context: fun的上下文
	 * }
	 */
	module.updateTex = function (tex, img, callback) {
		var p = {
			texture: tex,
			image: img
		};
		postMsg(renderWorker, "updateTex", callback, p);
	};

	/**
	 * 销毁纹理
	 * tex: int，纹理句柄
	 * callback: 带一个参数的函数，处理worker发送过来的回应数据
	 */
	module.destroyTex = function (tex, callback) {
		postMsg(renderWorker, "destroyTex", callback, tex);
	};

	/**
	 * 纹理变图像
	 * tex: int，纹理句柄
	 * callback: 带一个参数的函数，处理worker发送过来的回应数据
	 */
	module.getTexImage = function (tex, callback) {
		postMsg(renderWorker, "getTexImage", callback, tex);
	};

	/**
	 * 渲染
	 * data: {
	 *		context: 渲染环境句柄
	 *		bytes: 字节缓冲区句柄
	 * }
	 * callback: 带一个参数的函数，处理worker发送过来的回应数据
	 */
	module.render = function (data, callback) {
		postMsg(renderWorker, "render", callback, data);
	};

	return module;
});